﻿using GMap.NET;
using GMap.NET.Internals;
using GMap.NET.MapProviders;
using GMap.NET.WindowsForms;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Vishcious.ArcGIS.SLContrib;

namespace TilesDownloader
{
    public partial class MainForm : Form
    {
        public readonly GMapOverlay _polygons = new GMapOverlay("polygons");

        public MainForm()
        {
            InitializeComponent();

            if (!GMapControl.IsDesignerHosted)
            {
                // add your custom map db provider
                //GMap.NET.CacheProviders.MySQLPureImageCache ch = new GMap.NET.CacheProviders.MySQLPureImageCache();
                //ch.ConnectionString = @"server=sql2008;User Id=trolis;Persist Security Info=True;database=gmapnetcache;password=trolis;";
                //MainMap.Manager.SecondaryCache = ch;

                int zoom = 3;
                GPoint pp1 = BaiduProjection.Instance.FromLatLngToPixel(new PointLatLng(45, 0), zoom);
                GPoint pp2 = BaiduProjection.Instance.FromLatLngToPixel(new PointLatLng(30, 0), zoom);
                GPoint pp3 = BaiduProjection.Instance.FromLatLngToPixel(new PointLatLng(15, 0), zoom);
                GPoint pp4 = BaiduProjection.Instance.FromLatLngToPixel(new PointLatLng(0, 0), zoom);


                GPoint tt = BaiduProjection.Instance.FromPixelToTileXY(pp1);
                PointLatLng pl = BaiduProjection.Instance.FromPixelToLatLng(1023, 1024, 3);

                string x = tt.X.ToString().Replace('-', 'M');
                string y = tt.Y.ToString().Replace('-', 'M');
                string url = string.Format("http://online1.map.bdimg.com/tile/?qt=tile&x={0}&y={1}&z={2}&styles=pl",
                                           x, y, zoom);


                // config map 116.404, 39.915, 116.404
                MainMap.ShowTileGridLines = true;
                MainMap.MapProvider = GMapProviders.BaiduMap;                       // 默认地图
                MainMap.Position = new PointLatLng(39.915173, 116.403873);           // 地图中心点
                //MainMap.Position = new PointLatLng(39.915, 116.404);              // 地图中心点(北京)GPS坐标
                MainMap.MinZoom = GMapProviders.BaiduMap.MinZoom;                   // 地图最小比例
                MainMap.MaxZoom = GMapProviders.BaiduMap.MaxZoom ?? 24;             // 地图最大比例
                MainMap.Zoom = 3;                                                   // 当前缩放等级
                MainMap.DragButton = MouseButtons.Left;                             // 鼠标平移键

                MainMap.MouseMove += MainMap_MouseMove;


                MainMap.Overlays.Add(_polygons);


                //12178959.70,2773898.00
                //MainMap.FromLocalToLatLng

                //MainMap.Core.p..Position = new PointLatLng(27.7383440, 121.7954890);
                //MainMap.Zoom = 18;


            }

            InitMaps();
        }
        /// <summary>
        /// 
        /// </summary>
        private void InitMaps()
        {
            listViewMaps.Items.Clear();
            foreach (GMapProvider map in GMapProviders.List) {
                ListViewItem item = listViewMaps.Items.Add(map.Name);
                item.ImageIndex = 0;
                item.Tag = map;
            }
        }
        /// <summary>
        /// 
        /// </summary>
        private void MainMap_MouseMove(object sender, MouseEventArgs e)
        {
            PointLatLng pnew = MainMap.FromLocalToLatLng(e.X, e.Y);
            toolStripStatusLabelInfo.Text = string.Format("经度:{0:0.000000} 纬度:{1:0.000000}", pnew.Lng, pnew.Lat);
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="fileName"></param>
        private void AddSHPFile(string fileName)
        {
            System.IO.FileInfo fileInfo = new System.IO.FileInfo(fileName);
            ShapeFile shapeReader = new ShapeFile();
            shapeReader.ReadShapes(fileInfo);   // 该方法只读shape
            Collection<ShapeFileRecord> shapeRecords = shapeReader.Records;
            foreach (ShapeFileRecord record in shapeRecords)
            {
                //GMapPolygon polygon = new GMapPolygon(
                List<GMapPolygon> polygons = GetPolygon(record);
                foreach (GMapPolygon polygon in polygons) _polygons.Polygons.Add(polygon);

            }
        }
        /// <summary>
        /// 打开SHP文件
        /// </summary>
        private void toolStripButtonAddShp_Click(object sender, EventArgs e)
        {
            OpenFileDialog dialog = new OpenFileDialog();
            dialog.Filter = "SHP文件(*.shp)|*.shp";
            if (dialog.ShowDialog(this) != System.Windows.Forms.DialogResult.OK) return;
            AddSHPFile(dialog.FileName);
        }
        ///// <summary>
        ///// 
        ///// </summary>
        ///// <param name="record"></param>
        ///// <returns></returns>
        //private Graphic ToGraphic(this ShapeFileRecord record)
        //{
        //    if (record == null)
        //        return null;

        //    Graphic graphic = new Graphic();
        //    //add all the attributes to the graphic
        //    foreach (var item in record.Attributes)
        //    {
        //        graphic.Attributes.Add(item.Key, item.Value);
        //    }

        //    //add the geometry to the graphic
        //    switch (record.ShapeType)
        //    {
        //        case (int)ShapeType.NullShape:
        //            break;
        //        case (int)ShapeType.Multipoint:
        //            graphic.Geometry = GetMultiPoint(record);
        //            graphic.Symbol = DEFAULT_MARKER_SYMBOL;
        //            break;
        //        case (int)ShapeType.Point:
        //            graphic.Geometry = GetPoint(record);
        //            graphic.Symbol = DEFAULT_MARKER_SYMBOL;
        //            break;
        //        case (int)ShapeType.Polygon:
        //            graphic.Geometry = GetPolygon(record);
        //            graphic.Symbol = DEFAULT_FILL_SYMBOL;
        //            break;
        //        case (int)ShapeType.PolyLine:
        //            graphic.Geometry = GetPolyline(record);
        //            graphic.Symbol = DEFAULT_LINE_SYMBOL;
        //            break;
        //        default:
        //            break;
        //    }

        //    return graphic;
        //}

        /// <summary>
        /// 
        /// </summary>
        /// <param name="record"></param>
        /// <returns></returns>
        private List<GMapPolygon> GetPolygon(ShapeFileRecord record)
        {
            List<GMapPolygon> polygons = new List<GMapPolygon>();
            for (int i = 0; i < record.NumberOfParts; i++)
            {
                // Determine the starting index and the end index
                // into the points array that defines the figure.
                int start = record.Parts[i];
                int end;
                if (record.NumberOfParts > 1 && i != (record.NumberOfParts - 1)) end = record.Parts[i + 1];
                else end = record.NumberOfPoints;

                List<PointLatLng> points = new List<PointLatLng>();
                // Add line segments to the polyline
                for (int j = start; j < end; j++) {
                    points.Add(new PointLatLng(record.Points[j].Y, record.Points[j].X));
                }
                GMapPolygon polygon = new GMapPolygon(points, string.Format("{0}[{1}]", record.RecordNumber, i));
                polygons.Add(polygon);
            }
            return polygons;
        }
        /// <summary>
        /// 
        /// </summary>
        private void listViewMaps_SelectedIndexChanged(object sender, EventArgs e)
        {
            if (listViewMaps.SelectedItems.Count != 1) return;
            ListViewItem item = listViewMaps.SelectedItems[0];
            GMapProvider map = item.Tag as GMapProvider;
            if (map == null) return;
            MainMap.MapProvider = map;
            MainMap.MinZoom = map.MinZoom;              // 地图最小比例
            MainMap.MaxZoom = map.MaxZoom ?? 24;        // 地图最大比例
        }
    }
}
